package ar.com.algotres.tpdos.views.ventanas;

import static java.util.Arrays.asList;

import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Rectangle;
import java.util.List;

import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JToolBar;
import javax.swing.SwingUtilities;

import ar.com.algotres.tpdos.model.juego.Juego;
import ar.com.algotres.tpdos.model.juego.Nivel;
import ar.com.algotres.tpdos.persistence.CampoOmitido;
import ar.com.algotres.tpdos.persistence.IPersistidor;
import ar.com.algotres.tpdos.persistence.Persistidor;
import ar.com.algotres.tpdos.views.juego.IVistaJuego;
import ar.com.algotres.tpdos.views.juego.VistaJuego;
import ar.com.algotres.tpdos.views.observadores.ObservadorDeAterrizajes;
import ar.com.algotres.tpdos.views.observadores.ObservadorDeAterrizajesImpl;
import ar.com.algotres.tpdos.views.observadores.ObservadorDeAvionesVolando;
import ar.com.algotres.tpdos.views.observadores.ObservadorDeAvionesVolandoImpl;
import ar.uba.fi.algo3.titiritero.ControladorJuego;
import ar.uba.fi.algo3.titiritero.vista.Panel;

public class VentanaAplicacion extends JFrame {

	private ControladorJuego controlador;
	private Panel panel = null;
	private Juego juego;
	private ObservadorDeAterrizajes observadorDeAterrizajes;
	private ObservadorDeAvionesVolando observadorDeAvionesVolando;
	private IVistaJuego vistaJuego;

	private static final long serialVersionUID = 1L;
	private JPanel jContentPane = null;
	private JToolBar jJToolBarBar = null;
	private JMenuItem jMenuItem = null;
	private JMenuItem jMenuItemGuardar = null;
	private JMenuItem jMenuItemRecuperar = null;
	private JPanel jPanelAterrizados = null;
	private JComboBox<Integer> jComboNiveles = null;
	private JPanel jPanelNivel = null;
	private JLabel jLabelAterrizados = null;
	private JLabel jLabelNivel = null;
	private JPanel jPanelVolando = null;
	private JLabel jLabelVolando = null;

	private JToolBar getJJToolBarBar() {
		if (jJToolBarBar == null) {
			jJToolBarBar = new JToolBar();
			jJToolBarBar.setBounds(new Rectangle(0, 0, 300, 33));
			jJToolBarBar.add(getJMenuItem());
			jJToolBarBar.add(getjMenuItemGuardar());
			jJToolBarBar.add(getjMenuItemRecuperar());
		}
		return jJToolBarBar;
	}

	private JMenuItem getJMenuItem() {
		if (jMenuItem == null) {
			jMenuItem = new JMenuItem();
			jMenuItem.setText("Jugar");
			jMenuItem.addActionListener(new java.awt.event.ActionListener() {
				public void actionPerformed(java.awt.event.ActionEvent e) {
					comenzar();
				}
			});
		}
		return jMenuItem;
	}

	private JComboBox<Integer> getComboNiveles() {
		Integer[] numerosNiveles = { new Integer(1), new Integer(2),
				new Integer(3) };
		JComboBox<Integer> niveles = new JComboBox<Integer>(numerosNiveles);
		niveles.setBounds(0, 0, 50, 30);
		niveles.setVisible(true);
		niveles.setSelectedIndex(0);
		return niveles;
	}

	private void comenzar() {
		controlador.setSuperficieDeDibujo(getSuperficieDeDibujo());
		if (this.juego == null) {
			this.juego = new Juego(vistaJuego, observadorDeAterrizajes,
					observadorDeAvionesVolando);
			controlador.agregarObjetoVivo(this.juego);
			controlador.setIntervaloSimulacion(30);
		} else {
			this.vistaJuego.juegoTerminado();
		}

		Integer numeroNivel = (Integer) jComboNiveles.getSelectedItem();
		Nivel nivel = new Nivel(numeroNivel);

		this.juego.comenzar(nivel);

		controlador.comenzarJuegoAsyn();

	}

	private void recuperar() {
		if (juego == null) {
			juego = new Juego(vistaJuego, observadorDeAterrizajes,
					observadorDeAvionesVolando);
			controlador.agregarObjetoVivo(this.juego);
			controlador.setIntervaloSimulacion(30);
			controlador.setSuperficieDeDibujo(getSuperficieDeDibujo());
		} else {
			this.vistaJuego.juegoTerminado();
		}

		Persistidor persistidor = new Persistidor();
		Juego juegoRecuperado = (Juego) persistidor.recuperar("juego.xml");

		jComboNiveles
				.setSelectedIndex(juegoRecuperado.getNivel().getNumero() - 1);

		this.juego.recuperar(juegoRecuperado);

		controlador.comenzarJuegoAsyn();

	}

	private JMenuItem getjMenuItemGuardar() {
		if (jMenuItemGuardar == null) {
			jMenuItemGuardar = new JMenuItem();
			jMenuItemGuardar.setText("Guardar");
			jMenuItemGuardar
					.addActionListener(new java.awt.event.ActionListener() {
						public void actionPerformed(java.awt.event.ActionEvent e) {
							guardar();
						}
					});
		}
		return jMenuItemGuardar;
	}

	private JMenuItem getjMenuItemRecuperar() {
		if (jMenuItemRecuperar == null) {
			jMenuItemRecuperar = new JMenuItem();
			jMenuItemRecuperar.setText("Recuperar");
			jMenuItemRecuperar
					.addActionListener(new java.awt.event.ActionListener() {
						public void actionPerformed(java.awt.event.ActionEvent e) {
							recuperar();
						}
					});
		}
		return jMenuItemRecuperar;
	}

	private void guardar() {
		List<CampoOmitido> camposOmitidos = asList(new CampoOmitido(
				Juego.class, "vistaJuego"), new CampoOmitido(Juego.class,
				"observadorAterrizajes"));
		IPersistidor persistidor = new Persistidor(camposOmitidos);

		System.out.println("Salvando juego...");
		persistidor.guardar(juego, "juego.xml");
		System.out.println("Juego guardado correctamente.");
	}

	private Panel getSuperficieDeDibujo() {
		if (panel == null) {
			panel = new Panel(500, 500, controlador);
			panel.setLayout(new GridBagLayout());
			panel.setBounds(new Rectangle(250, 38, 800, 600));
		}
		return panel;
	}

	private JPanel getJPanelAterrizados() {
		if (jPanelAterrizados == null) {
			GridBagConstraints gridBagConstraints1 = new GridBagConstraints();
			gridBagConstraints1.gridx = 1;
			gridBagConstraints1.gridy = 0;
			observadorDeAterrizajes = new ObservadorDeAterrizajesImpl();
			GridBagConstraints gridBagConstraints = new GridBagConstraints();
			gridBagConstraints.gridx = 0;
			gridBagConstraints.gridy = 0;
			jLabelAterrizados = new JLabel();
			jLabelAterrizados.setText("Aviones aterrizados: ");
			jPanelAterrizados = new JPanel();
			jPanelAterrizados.setLayout(new GridBagLayout());
			jPanelAterrizados.setBounds(new Rectangle(8, 161, 200, 40));
			jPanelAterrizados.add(jLabelAterrizados, gridBagConstraints);
			jPanelAterrizados.add(observadorDeAterrizajes.getLabel(),
					gridBagConstraints1);
		}
		return jPanelAterrizados;
	}

	private JPanel getJPanelVolando() {
		if (jPanelVolando == null) {

			observadorDeAvionesVolando = new ObservadorDeAvionesVolandoImpl();
			GridBagConstraints gridBagConstraints = new GridBagConstraints();
			gridBagConstraints.gridx = 0;
			gridBagConstraints.gridy = 0;
			GridBagConstraints gridBagConstraints1 = new GridBagConstraints();
			gridBagConstraints1.gridx = 1;
			gridBagConstraints1.gridy = 0;
			jLabelVolando = new JLabel();
			jLabelVolando.setText("Aviones volando: ");
			jPanelVolando = new JPanel();
			jPanelVolando.setLayout(new GridBagLayout());
			jPanelVolando.setBounds(new Rectangle(8, 121, 200, 40));
			jPanelVolando.add(jLabelVolando, gridBagConstraints);
			jPanelVolando.add(observadorDeAvionesVolando.getLabel(),
					gridBagConstraints1);
		}
		return jPanelVolando;
	}

	private JPanel getJPanelNiveles() {
		if (jPanelNivel == null) {
			GridBagConstraints gridBagConstraints1 = new GridBagConstraints();
			gridBagConstraints1.gridx = 1;
			gridBagConstraints1.gridy = 0;
			GridBagConstraints gridBagConstraints = new GridBagConstraints();
			gridBagConstraints.gridx = 0;
			gridBagConstraints.gridy = 0;
			jLabelNivel = new JLabel();
			jLabelNivel.setText("Nivel:  ");
			jPanelNivel = new JPanel();
			jPanelNivel.setLayout(new GridBagLayout());
			jPanelNivel.setBounds(new Rectangle(8, 61, 200, 40));
			jPanelNivel.add(jLabelNivel, null);
			jComboNiveles = getComboNiveles();
			jPanelNivel.add(jComboNiveles, null);
		}
		return jPanelNivel;
	}

	public static void main(String[] args) {
		SwingUtilities.invokeLater(new Runnable() {
			public void run() {
				VentanaAplicacion thisClass = new VentanaAplicacion();
				thisClass.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
				thisClass.setVisible(true);
			}
		});
	}

	public VentanaAplicacion() {
		super();
		initialize();
	}

	private void initialize() {
		controlador = new ControladorJuego(false);
		vistaJuego = new VistaJuego(controlador, this);
		this.setSize(1100, 700);
		this.setResizable(false);
		this.setContentPane(getJContentPane());
		this.setTitle("Cop-Control");
		this.addWindowListener(new java.awt.event.WindowAdapter() {
			public void windowClosing(java.awt.event.WindowEvent e) {
				System.exit(NORMAL);
			}
		});
	}

	private JPanel getJContentPane() {
		if (jContentPane == null) {
			jContentPane = new JPanel();
			jContentPane.setLayout(null);
			jContentPane.add(getJJToolBarBar(), null);
			jContentPane.add(getSuperficieDeDibujo(), null);
			jContentPane.add(getJPanelAterrizados(), null);
			jContentPane.add(getJPanelVolando(), null);
			jContentPane.add(getJPanelNiveles(), null);
		}
		return jContentPane;
	}

}
